<template>
  <a-form :form="form">
    <a-form-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="请求超时时间">
      <a-input-number v-decorator="['requestTimeout', validatorRules.requestTimeout]" style="width: 100%" :min="0" :disabled="disableSubmit" />
    </a-form-item>
    <a-form-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="服务Url">
      <a-input placeholder="请输入服务Url" v-decorator="['apiUrl', validatorRules.apiUrl]" :disabled="disableSubmit" />
    </a-form-item>
    <a-form-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="是否为授权服务">
      <j-switch :options="[1, 0]"  v-decorator="['isAuthorized', validatorRules.isAuthorized]" :disabled="disableSubmit"  @change="changeIsAuthorized"/>
    </a-form-item>
    <a-form-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="授权方式" v-if="isAuthorized == 0">
      <a-radio-group v-decorator="['authorizationMethod', validatorRules.authorizationMethod]" :disabled="disableSubmit" :trigger-change="true"  @change="changeAuthorizationMethod">
        <a-radio value="0">无需授权</a-radio>
        <a-radio value="1">提供方授权</a-radio>
        <!-- <a-radio value="3">平台授权</a-radio> -->
      </a-radio-group>
    </a-form-item>
    <a-form-item label="授权接口" :labelCol="labelCol" :wrapperCol="wrapperCol" v-if="isAuthorized == 0 && authorizationMethod != 0">
      <a-select placeholder="请选择授权接口" v-decorator="['authorizationApiId', validatorRules.authorizationApiId]" :disabled="disableSubmit">
        <a-select-option v-for="item in apis" :key="'id' + item.id" :value="item.id">{{ item.apiName }}</a-select-option>
      </a-select>
    </a-form-item>
    <a-form-item label="请求方式" :labelCol="labelCol" :wrapperCol="wrapperCol">
      <j-dict-select-tag :trigger-change="true" v-decorator="['apiMethod', validatorRules.apiMethod]" placeholder="请选择请求方式" dict-code="api_method" :disabled="disableSubmit" />
    </a-form-item>
    <a-form-item label="GET参数" :labelCol="labelCol" :wrapperCol="wrapperCol">
      <InterfaceParams ref="interfaceGetParam" :data-source="getParams" @edit="editGetParams" @add="addGetParams" @delete="deleteGetParams" :disableSubmit="disableSubmit" />
    </a-form-item>
    <a-form-item label="Header" :labelCol="labelCol" :wrapperCol="wrapperCol">
      <InterfaceParams ref="interfaceHeaderParam" :data-source="headerParams" @edit="editHeaderParams" @add="addHeaderParams" @delete="deleteHeaderParams" :disableSubmit="disableSubmit" />
    </a-form-item>
    <a-form-item label="Body" :labelCol="labelCol" :wrapperCol="wrapperCol">
      <j-dict-select-tag type="radio" v-model="bodyType"  dict-code="api_content_type" />
      <InterfaceParams ref="interfaceBodyParam" v-show="bodyType == 0 || bodyType == 2" @edit="editBodyParams" :data-source="bodyParams" @add="addBodyParams" @delete="deleteBodyParams" :disableSubmit="disableSubmit" />
      <JsonEditor v-model="bodyJson" v-show="bodyType == 1"  :readOnly="disableSubmit" />
    </a-form-item>
    <a-form-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="接口文档">
      <j-upload v-model="fileList"></j-upload>
    </a-form-item>
    <a-form-item label="返回结果" :labelCol="labelCol" :wrapperCol="wrapperCol">
      <a-button type="primary" style="margin-bottom: 8px" @click="viewResultData">数据预览</a-button>
    </a-form-item>
    <a-form-item label="参数路径" :labelCol="labelCol" :wrapperCol="wrapperCol">
      <a-input placeholder="请输入参数路径" v-model="jsonTreeName" style="width: calc(100% - 110px)" :disabled="disableSubmit" />
      <a-button type="primary" style="margin-bottom: 8px;width: 90px;;margin-left: 10px" @click="formatJson1">生成结果</a-button>
      <ApiRepsTable ref="apiRepsTable" :actionButton="!disableSubmit" />
    </a-form-item>
  </a-form>
</template>

<script>
import JsonEditor from '@/components/JsonEditor.vue'
import pick from 'lodash.pick'
import { queryDepartTreeList } from '@/api/api'
import InterfaceParams from './InterfaceParams'
import { getAction, postAction } from '@/api/manage'
import ApiRepsTable from './ApiRepsTable'
export default {
  name: 'InterfaceBaseForm',
  components: {
    InterfaceParams,
    JsonEditor,
    ApiRepsTable
  },
  props: {
    disableSubmit: {
      type: Boolean,
      default: false
    }
  },
  data() {
    return {
      authorizationMethod: 0,
      jsonTreeName: null,
      interfaceId: null,
      resultJson: null,
      fileList: [],
      isAuthorized: 0,
      bodyJson: null,
      bodyType: 1,
      apis: [],
      getParams: [],
      headerParams: [],
      bodyParams: [],
      model: {},
      labelCol: {
        xs: { span: 24 },
        sm: { span: 4 }
      },
      wrapperCol: {
        xs: { span: 24 },
        sm: { span: 18 }
      },
      confirmLoading: false,
      form: this.$form.createForm(this),
      validatorRules: {
        apiMethod: { rules: [{ required: true, message: '请选择请求方式!' }] },
        apiUrl: { rules: [
          { required: true, message: '请输入接口URL地址!' },
          { validator: this.isUrl }
        ] }
      },
      url: {
        add: '/sys/dataSource/add',
        edit: '/sys/dataSource/edit'
      }
    }
  },
  created() {
  },
  methods: {
    changeAuthorizationMethod(val) {
      this.authorizationMethod = val.target.value
    },
    formatJson1() {
      if (this.jsonTreeName == null || this.jsonTreeName == '') {
        this.$message.error('请输入参数路径')
        return
      }
      this.$emit('formatJson')
      // if (this.resultJson == null || this.resultJson == '') {
      //   this.$message.error('返回数据为空')
      //   return
      // }
      // console.log(this.formatJson(jsonTemp, this.jsonTreeName))
    },
    formatJsonResult(resultJson) {
      var jsonTemp = resultJson
      var resultTemp = this.formatJson(jsonTemp, this.jsonTreeName)
      if (resultTemp) {
        var dataTemp = []
        for (var key in resultTemp) {
          dataTemp.push({
            repRoute: this.jsonTreeName + '.' + key,
            name: '',
            code: key,
            type: '',
            defaultValue: resultTemp[key],
            dataFormat: '',
            unit: ''
          })
        }
        this.$refs.apiRepsTable.initValues(dataTemp)
      }
    },
    /** 解析json */
    formatJson(jsonData, nameStr) {
      if (nameStr.indexOf('.') != -1) {
        var nameTemp = nameStr.substring(0, nameStr.indexOf('.'))
        console.log('nameTemp----------------------------', nameTemp)
        if (nameTemp == '$') {
          return this.formatJson(jsonData, nameStr.substring(nameStr.indexOf('.') + 1))
        } else {
          return this.formatJson(this.checkIsArray(jsonData, nameTemp), nameStr.substring(nameStr.indexOf('.') + 1))
        }
      } else {
        return this.checkIsArray(jsonData, nameStr)
        // return jsonData[nameStr]
      }
    },
    checkIsArray(jsonData, nameStr) {
      if (nameStr.indexOf('[') != -1) {
        var namesTemp = nameStr.split('[')
        if (namesTemp[1].split(']')[0] == '*') {
          return jsonData[namesTemp[0]][0]
        }
        return jsonData[namesTemp[0]][namesTemp[1].split(']')[0]]
      } else {
        console.log(jsonData)
        console.log(nameStr)
        console.log(jsonData[nameStr])
        return jsonData[nameStr]
      }
    },
    viewResultData() {
      this.$emit('viewResultData')
    },
    getApis() {
      // apis /dataSource/scApi/list
      var params = {
        pageNo: 1,
        pageSize: 10000000,
        isAuthorized: 1
      }
      getAction('/dataSource/scApi/list', params).then(res => {
        if (res.success) {
          this.apis = res.result.records
        }
      })
    },
    changeIsAuthorized(val) {
      this.isAuthorized = val
    },
    getAllParams() {
      var allParams = []
      this.getParams.forEach(item => {
        item.requestType = 'params'
        allParams.push(item)
      })
      this.headerParams.forEach(item => {
        item.requestType = 'headers'
        allParams.push(item)
      })
      if (this.bodyType == '1') {
        allParams.push({
          bodyType: this.bodyType,
          bodyJson: this.bodyJson,
          requestType: 'body'
        })
      } else {
        this.bodyParams.forEach(item => {
          item.bodyType = this.bodyType
          item.requestType = 'body'
          allParams.push(item)
        })
      }

      return allParams
    },
    isUrl(rule, value, callback) {
      const regex = new RegExp('^(?!mailto:)(?:(?:http|https|ftp)://|//)(?:\\S+(?::\\S*)?@)?(?:(?:(?:[1-9]\\d?|1\\d\\d|2[01]\\d|22[0-3])(?:\\.(?:1?\\d{1,2}|2[0-4]\\d|25[0-5])){2}(?:\\.(?:[0-9]\\d?|1\\d\\d|2[0-4]\\d|25[0-4]))|(?:(?:[a-z\\u00a1-\\uffff0-9]+-?)*[a-z\\u00a1-\\uffff0-9]+)(?:\\.(?:[a-z\\u00a1-\\uffff0-9]+-?)*[a-z\\u00a1-\\uffff0-9]+)*(?:\\.(?:[a-z\\u00a1-\\uffff]{2,})))|localhost)(?::\\d{2,5})?(?:(/|\\?|#)[^\\s]*)?$', 'i')
      if (regex.test(value)) {
        callback()
      } else {
        callback('URL地址格式错误')
      }
    },
    /** ********************************************操作传参内容**********************************************************************/
    deleteGetParams(values) {
      values.forEach(val => {
        this.getParams.splice(this.getParams.findIndex(item => item.code == val), 1)
      })
    },
    deleteHeaderParams(values) {
      values.forEach(val => {
        this.headerParams.splice(this.headerParams.findIndex(item => item.code == val), 1)
      })
    },
    deleteBodyParams(values) {
      values.forEach(val => {
        this.bodyParams.splice(this.bodyParams.findIndex(item => item.code == val), 1)
      })
    },
    editGetParams(val) {
      if (this.getParams.find(item => (item.code == val.code && item.timeCode != val.timeCode))) {
        this.$message.warning('参数名重复')
      } else {
        var indexTemp = this.getParams.findIndex(item => item.timeCode == val.timeCode)
        this.getParams.splice(indexTemp, 1, val)
        // this.getParams[indexTemp] = val
        this.$refs.interfaceGetParam.close()
      }
    },
    editHeaderParams(val) {
      if (this.headerParams.find(item => (item.code == val.code && item.timeCode != val.timeCode))) {
        this.$message.warning('参数名重复')
      } else {
        var indexTemp = this.headerParams.findIndex(item => item.timeCode == val.timeCode)
        this.headerParams.splice(indexTemp, 1, val)
        this.$refs.interfaceHeaderParam.close()
      }
    },
    editBodyParams(val) {
      if (this.bodyParams.find(item => (item.code == val.code && item.timeCode != val.timeCode))) {
        this.$message.warning('参数名重复')
      } else {
        var indexTemp = this.bodyParams.findIndex(item => item.timeCode == val.timeCode)
        this.bodyParams.splice(indexTemp, 1, val)
        this.$refs.interfaceBodyParam.close()
      }
    },
    addGetParams(val) {
      if (this.getParams.find(item => item.code == val.code)) {
        this.$message.warning('参数名重复')
      } else {
        val.timeCode = this.getUuid()
        this.getParams.push(val)
        this.$refs.interfaceGetParam.close()
      }
    },
    addHeaderParams(val) {
      if (this.headerParams.find(item => item.code == val.code)) {
        this.$message.warning('参数名重复')
      } else {
        val.timeCode = this.getUuid()
        this.headerParams.push(val)
        this.$refs.interfaceHeaderParam.close()
      }
    },
    addBodyParams(val) {
      if (this.bodyParams.find(item => item.code == val.code)) {
        this.$message.warning('参数名重复')
      } else {
        val.timeCode = this.getUuid()
        this.bodyParams.push(val)
        this.$refs.interfaceBodyParam.close()
      }
    },
    /** ******************************************************************************************************************/
    add() {
      this.getApis()
      this.form.resetFields()
      this.fileList = []
      this.getParams = []
      this.headerParams = []
      this.bodyParams = []
      this.isAuthorized = 0
      this.authorizationMethod = 0
      this.bodyJson = null
      this.model = { isAuthorized: 0 }
      this.$refs.apiRepsTable.reset()
      this.$nextTick(() => {
        this.form.setFieldsValue(pick(this.model, 'requestTimeout', 'apiUrl', 'isAuthorized', 'authorizationMethod', 'authorizationApiId', 'apiMethod'))
      })
    },
    edit(record) {
      this.getApis()
      this.interfaceId = record.apiInfo.id
      this.form.resetFields()
      this.model = Object.assign({}, record.apiInfo)
      this.fileList = record.apiInfo.interfaceDocumentationPath

      // 处理getParams
      this.getParams = record.scApiReqList.filter(item => item.requestType == 'params')
      this.getParams.forEach(item => {
        item.timeCode = this.getUuid()
      })

      // 处理headerParams
      this.headerParams = record.scApiReqList.filter(item => item.requestType == 'headers')
      this.headerParams.forEach(item => {
        item.timeCode = this.getUuid()
      })

      // 处理bodyParam
      var bodyParam = record.scApiReqList.filter(item => item.requestType == 'body')
      if (bodyParam != null && bodyParam.length > 0) {
        this.bodyType = bodyParam[0].bodyType
        if (this.bodyType == '1') {
          this.bodyJson = bodyParam[0].bodyJson
        } else {
          this.bodyParams = bodyParam
          this.bodyParams.forEach(item => {
            item.timeCode = this.getUuid()
          })
        }
      }

      this.$refs.apiRepsTable.reset()
      this.$refs.apiRepsTable.initValues(record.scApiRepList == null ? [] : record.scApiRepList)

      this.visible = true
      this.$nextTick(() => {
        this.form.setFieldsValue(pick(this.model, 'requestTimeout', 'apiUrl', 'isAuthorized', 'authorizationMethod', 'authorizationApiId', 'apiMethod'))
        this.isAuthorized = record.apiInfo.isAuthorized
        this.authorizationMethod = record.apiInfo.authorizationMethod
      })
    },
    getApiRepsTableData() {
      return this.$refs.apiRepsTable.getValues()
    },
    close() {
      this.$emit('close')
      this.resultJson = null
      this.interfaceId = null
      this.visible = false
    },
    handleCancel() {
      this.close()
    },
    /**
     * 获取UUID
     */
    getUuid() {
      return (this.S4() + this.S4() + '-' + this.S4() + '-' + this.S4() + '-' + this.S4() + '-' + this.S4() + this.S4() + this.S4())
    },
    S4() {
      return (((1 + Math.random()) * 0x10000) | 0).toString(16).substring(1)
    }
  }
}
</script>

<style lang="less" scoped>
.atn-testbtn {
    color: #2F77F2 !important;
    background: #FFFFFF !important;
    box-shadow: 0px 1px 3px 0px rgba(4, 0, 0, 0.08) !important;
    border: 1px solid #2F77F2 !important;
    border-radius: 2px !important;
    padding: 0 10px !important;
    height: 34px !important;
    margin: 0 8px 8px 0;
}
</style>
